package models

import (
	"errors"
	"fmt"
	"github.com/astaxie/beego/httplib"
	"github.com/labstack/gommon/log"
	uuid2 "github.com/satori/go.uuid"
	"github.com/xlstudio/wxbizdatacrypt"
	"quiz/common"
	"quiz/conf"
	"strings"
)

type Resp struct {
	Openid     string `json:"openid"`      //用户唯一标识
	Sessionkey string `json:"session_key"` //会话密钥
	Unionid    string `json:"unionid"`     //用户在开放平台的唯一标识符，在满足 UnionID 下发条件的情况下会返回，详见 UnionID 机制说明。
	Errcode    int    `json:"errcode"`     //错误码
	ErrMsg     string `json:"errMsg"`      //错误信息
}

/**
拼接登陆Url
*/
func InitLoginUrl(code string) (url string) {
	url = fmt.Sprintf(common.LoginUrl, common.Appid, common.Secret, code)
	return
}

/**
通过code换取登陆凭证
*/
func CodeToSession(code string) (loginResp Resp, err error) {
	url := InitLoginUrl(code)
	resp := httplib.Get(url)
	err = resp.ToJSON(&loginResp)
	if err != nil {
		return loginResp, err
	}

	if loginResp.Errcode != 0 {
		return loginResp, errors.New(fmt.Sprint("code: %d,errmsg:%s", loginResp.Errcode, loginResp.ErrMsg))
	}

	return loginResp, nil
}

func AesDecrypt(encryptedData string, sessionKey string, iv string) (result interface{}, err error) {
	pc := wxbizdatacrypt.WxBizDataCrypt{AppID: common.Appid, SessionKey: sessionKey}
	result, err = pc.Decrypt(encryptedData, iv, false) //第三个参数解释： 需要返回 JSON 数据类型时 使用 true, 需要返回 map 数据类型时 使用 false
	if err != nil {
		fmt.Println(err)
	} else {
		fmt.Println(result)
	}
	return result, err
}

/**
将SessionKey保存到redis
*/
func SaveSessionKeyToCache(key string, opionId string) (token string) {
	uuid, err := uuid2.NewV4()
	if err != nil {
		log.Info("生成UUID失败!", err)
		return
	}
	token = opionId + "_" + strings.Replace(uuid.String(), "-", "", -1)
	conf.Setcc(token, key, -1)
	return token
}

func GetSessionKey(token string) (key string) {
	err := conf.Getcc(token, &key)
	if err != nil {
		log.Info("获取缓存失败!", err)
	}
	return key
}
